package com.tanhua.server.service;

import cn.hutool.core.collection.CollUtil;
import com.tanhua.dubbo.api.*;
import com.tanhua.model.domain.UserInfo;
import com.tanhua.model.mongo.*;
import com.tanhua.model.vo.ConclusionVo;
import com.tanhua.model.vo.ErrorResult;
import com.tanhua.model.vo.QuestionnaireVo;
import com.tanhua.model.vo.QuestionsVo;
import com.tanhua.server.exception.BusinessException;
import com.tanhua.server.interceptor.UserHolder;
import org.apache.dubbo.config.annotation.DubboReference;
import org.bson.types.ObjectId;
import org.springframework.stereotype.Service;

import java.util.ArrayList;
import java.util.List;

@Service
public class TestSoulService {

    @DubboReference
    private QuestionnaireApi questionnaireApi;
    @DubboReference
    private QuestionsApi questionsApi;
    @DubboReference
    private OptionsApi optionsApi;
    @DubboReference
    private UsersScoreApi usersScoreApi;
    @DubboReference
    private ConclusionApi conclusionApi;
    @DubboReference
    private DimensionsApi dimensionsApi;
    @DubboReference
    private UserInfoApi userInfoApi;
    //我写的代码今天只有我和上帝认识,明天就只有上帝认识了
    //问卷列表
    public List<QuestionnaireVo> findQuestionnaire() {
        //查找所有的问卷
        List<Questionnaire> items = questionnaireApi.findQuestionnaire();
        if (CollUtil.isEmpty(items)) {
            //为空直接返回空集合
            return new ArrayList<>();
        }
        //构建返回值Vo
        List<QuestionnaireVo> list = new ArrayList<>();
        int i = 1;
        //遍历问卷集合
        for (Questionnaire item : items) {
            //根据问卷id 获取到相对应的题目集合
            List<Questions> questions = questionsApi.findQuestions(item.getId());
            //如果集合为空 抛出异常
            if (CollUtil.isEmpty(questions)){
                throw new BusinessException(ErrorResult.error());
            }

            List<QuestionsVo> questionsVo = new ArrayList<>();
            //遍历题目的集合
            for (Questions question : questions) {
                List<Options> options = optionsApi.findOptions(question.getId());
                if (CollUtil.isEmpty(options)){
                    throw new BusinessException(ErrorResult.error());
                }
                //构造出QuestionVo
                QuestionsVo vo = QuestionsVo.init(question, options);
                questionsVo.add(vo);
            }
            //根据问卷id 用户id查询出用户结果表 用于判断后续是否解锁 结果1
            UsersScore usersScores = usersScoreApi.findUsersScore(item.getId(),UserHolder.getUserId());
            //兜底 只根据用户id来查找用户结果表 结果2
            UsersScore score = usersScoreApi.findOneByuserId(UserHolder.getUserId());
            //设置初始值
            //如果结果1为null 则说明当前问卷该用户没有测试过 ,但是初始值即初级灵魂题应当是解锁状态 所以根据初级以及问卷名称判断是否相同
            //相同则代表该用户首次进行测试,为其构建用户结果的对象,以解锁问卷
            if ("初级灵魂题".equals(item.getName()) && usersScores == null) {
                usersScores = new UsersScore();
                usersScores.setIsLock(0);
            //如果结果1为null 并且该用户测试过了 则需要判断 用户做过的问卷
            } else if (usersScores==null){
                //构建用户结果对象,先将其设置为1 上锁状态
                usersScores = new UsersScore();
                usersScores.setIsLock(1);
                //如果 结果2不为null(一般也不为null) 并且结果中的问卷id 与当前问卷的id不相等
                if (score != null && score.getQuestionnaireId() != item.getId()) {
                    //则需要获取到 结果2对应的问卷对象
                    Questionnaire questionnaire = questionnaireApi.findById(score.getQuestionnaireId());
                    //如果问卷对象的名称是中级灵魂题 则说明当前用户已经完成了中级试卷 当前问卷(高级问卷)应当解锁
                    if (questionnaire!=null && "中级灵魂题".equals(questionnaire.getName())){
                        usersScores.setIsLock(0);
                        //如果问卷对象的名称是初级灵魂题 则说明当前用户已经完成了初级试卷 当前问卷(中级问卷)应当解锁
                    }else if (questionnaire!=null && "初级灵魂题".equals(questionnaire.getName())){

                        i++;
                        //i==3时并且进入了初级灵魂题 ,为了防止误解锁高级问卷 需要将其跳过设置
                        if (i!=3){

                            usersScores.setIsLock(0);
                        }
                    //如果获取的最新结果表 为高级灵魂表 则直接设置为解锁状态即可
                    }else if (questionnaire!=null && "高级灵魂题".equals(questionnaire.getName())){
                        usersScores.setIsLock(0);

                    }
                }
            }


            //构造Vo 添加到list集合中
            QuestionnaireVo vo = QuestionnaireVo.init(questionsVo, usersScores, item);
            list.add(vo);
        }
        return list;
    }

    //提交问卷
    public String commitResult(List<String> optionId, List<String> questionId) {
        //首先判断选项的id是否为空 空则报异常
        if (CollUtil.isEmpty(optionId)) {
            throw new BusinessException(ErrorResult.error());
        }

        List<ObjectId> optionsId = new ArrayList<>();
        //类型转换
        for (String s : optionId) {
            ObjectId objectId = new ObjectId(s);
            optionsId.add(objectId);
        }
        //获取到选项的集合
        List<Options> options = optionsApi.findByIds(optionsId);

        if (CollUtil.isEmpty(options)) {
            throw new BusinessException(ErrorResult.error());
        }

        int sum = 0;
        //累加分数
        for (Options option : options) {
            sum = option.getScore() + sum;
        }

        if (CollUtil.isEmpty(questionId)) {
            throw new BusinessException(ErrorResult.error());
        }
        //根据题目id获取到题目对象 目的是获取到问卷的id
        Questions questions = questionsApi.findById(new ObjectId(questionId.get(0)));
        //封装UserScore对象
        UsersScore usersScore = new UsersScore();
        usersScore.setUserScore(sum);
        usersScore.setUserId(UserHolder.getUserId());
        usersScore.setIsLock(0);

        if (questions != null) {
            usersScore.setQuestionnaireId(questions.getQuestionnaireId());
        }
        usersScore.setCreated(System.currentTimeMillis());
        //保存
        Boolean aBoolean = usersScoreApi.save(usersScore);
        //false则抛异常
        if (!aBoolean) {
            throw new BusinessException(ErrorResult.error());
        }
        //拿到最新保存的对象 获取到id 返回出去
        UsersScore usersScore1 = usersScoreApi.findOneByuserId(UserHolder.getUserId());
        if (usersScore1!=null){
            return usersScore1.getId().toString();
        }
        return null;

    }

    //查看结果
    public ConclusionVo report(String reportId) {

        if (reportId == null) {
            throw new BusinessException(ErrorResult.error());
        }
        //获取到得分结果的对象
        UsersScore usersScore = usersScoreApi.findById(new ObjectId(reportId));
        if (usersScore == null) {
            throw new BusinessException(ErrorResult.error());
        }
        //拿到总分
        Integer userScore = usersScore.getUserScore();
        Conclusion conclusion = conclusionApi.findByScore(userScore);
        if (conclusion == null) {
            throw new BusinessException(ErrorResult.error());
        }

        ObjectId conclusionId = conclusion.getId();
        //获取到维度对象集合
        List<Dimensions> dimensions = dimensionsApi.findById(conclusionId);
        if (CollUtil.isEmpty(dimensions)){
            throw new BusinessException(ErrorResult.error());
        }
        //获取到这个分段的所有用户得分对象
        List<UsersScore> usersScoreList = usersScoreApi.findByUserScore(userScore);
        List<Long> userId = new ArrayList<>();
        if (!CollUtil.isEmpty(usersScoreList)) {
            userId = CollUtil.getFieldValues(usersScoreList, "userId", Long.class);
        }
        //排除掉自己的id
        List<Long> userIds = new ArrayList<>();
        for (Long ids : userId) {
            if (ids.equals(UserHolder.getUserId())){
                continue;
            }
            userIds.add(ids);
        }

        List<UserInfo> userInfoList = new ArrayList<>();
        if (userIds!=null){
            //根据用户id集合获取用户详情集合
            userInfoList = userInfoApi.findByIdsList(userIds);
        }
        //构造vo返回
        ConclusionVo vo = ConclusionVo.init(conclusion, dimensions, userInfoList);
        return vo;

    }
}
